package org.noote.libs.computervision.detection.line;

import org.noote.libs.computervision.detection.edge.SobelDetection;
import org.noote.libs.computervision.math.Segment2D;

public class LineDetection_Base extends SobelDetection {

	protected int _sobel_limit_min = 25;
	
	public class Segment extends Segment2D
	{
		public boolean expand(float maxlen)
		{
			return expand(0, 0, _width, _height, maxlen);
		}
		public boolean expand(int bx, int by, int ex, int ey, float maxlen)
		{
			return expand(bx, by, ex, ey, maxlen, true, true);
		}
		public boolean expand(int bx, int by, int ex, int ey, float maxlen, boolean expand_start, boolean expand_end)
		{
			boolean bStartExpanded = false;
			boolean bEndExpanded = false;
			
			// continue from start
			float start_x = start.x;
			float start_y = start.y;
			if(expand_start)
			{
				for(int s=0; s<maxlen; s++)
				{
					float t_start_x=start_x-slope.x;
					float t_start_y=start_y-slope.y;
					
					if(start_x<bx || start_y<by || start_x>ex || start_y>ey)
						break;
					
					int idx = (int)(start_y)*_width + (int)(start_x);				
					if(_iEdge[idx]<=_sobel_limit_min)
						break;
					
					// point valid :)
					start_x = t_start_x;
					start_y = t_start_y;
					bStartExpanded = true;
				}
			}

			// continue from end
			float end_x = end.x;
			float end_y = end.y;
			if(expand_end)
			{
				for(int e=0; e<maxlen; e++)
				{
					float t_end_x=end_x+slope.x;
					float t_end_y=end_y+slope.y;
					
					if(end_x<bx || end_y<by || end_x>ex || end_y>ey)
						break;
	
					int idx = (int)(end_y)*_width + (int)(end_x);				
					if(_iEdge[idx]<=_sobel_limit_min)
						break;
					
					end_x = t_end_x;
					end_y = t_end_y;
					
					bEndExpanded = true;
				}
			}
			
			if(bStartExpanded || bEndExpanded)
			{
				if(bStartExpanded)
				{
					start.x = (int)start_x;
					start.y = (int)start_y;
				}
				if(bEndExpanded)
				{
					end.x = (int)end_x;
					end.y = (int)end_y;
				}
				rebuild();
			}
			
			return (bStartExpanded || bEndExpanded);
		}
	}
}
